package com.rrsllc.toggle4g;

import android.app.PendingIntent;
import android.appwidget.*;
import android.content.*;
import android.content.pm.*;
import android.net.*;
import android.util.Log;
import android.widget.RemoteViews;
import android.widget.Toast;

import java.lang.reflect.*;

public class Toggle4GWidgetProvider extends AppWidgetProvider {
	static final String TAG = "Toggle4GWidgetProvider";
	
	static final ComponentName THIS_WIDGET = new ComponentName("com.rrsllc.toggle4g",
			"com.rrsllc.toggle4g.Toggle4GWidgetProvider");
	
	private static final int BUTTON_WIMAX = 0;
	
	private static final int STATE_DISABLED = 0;
	private static final int STATE_ENABLED = 1;
	private static final int STATE_INTERMEDIATE = 2;
	
	private static final String CONTEXT_WIMAX_SERVICE = "wimax";
	
	private static final int WIMAX_STATE_DISABLED = 1;
	private static final int WIMAX_STATE_ENABLED = 3;
	
	@Override
	public void onReceive(Context context, Intent intent) {
		super.onReceive(context, intent);
		
		if (intent.hasCategory(Intent.CATEGORY_ALTERNATIVE)) {
			Uri data = intent.getData();
			int buttonId = Integer.parseInt(data.getSchemeSpecificPart());
			
			if (buttonId == BUTTON_WIMAX) {
				toggleWimax(context);
			}
		}
		
		updateWidget(context);
	}
		
	@Override
	public void onUpdate(Context context, AppWidgetManager appWidgetManager, int[] appWidgetIds) {
		RemoteViews view = buildUpdate(context, -1);
		
		for (int i = 0; i < appWidgetIds.length; i++) {
			appWidgetManager.updateAppWidget(appWidgetIds[i], view);
		}
	}
	
	@Override
	public void onEnabled(Context context) {
		PackageManager pm = context.getPackageManager();
        pm.setComponentEnabledSetting(
                new ComponentName("com.rrsllc.toggle4g", ".Toggle4GWidgetProvider"),
                PackageManager.COMPONENT_ENABLED_STATE_ENABLED,
                PackageManager.DONT_KILL_APP);
	}
	
	@Override
    public void onDisabled(Context context) {
        PackageManager pm = context.getPackageManager();
        pm.setComponentEnabledSetting(
        		new ComponentName("com.rrsllc.toggle4g", ".Toggle4GWidgetProvider"),
                PackageManager.COMPONENT_ENABLED_STATE_DISABLED,
                PackageManager.DONT_KILL_APP);
    }
	
	static RemoteViews buildUpdate(Context context, int appWidgetId) {
		RemoteViews views = new RemoteViews(context.getPackageName(), R.layout.widget);
		
		views.setOnClickPendingIntent(R.id.btn_wimax, getLaunchPendingIntent(context, appWidgetId, BUTTON_WIMAX));
		
		updateButtons(views, context);
		return views;
	}
	
	public static void updateWidget(Context context) {
		RemoteViews views = buildUpdate(context, -1);
		final AppWidgetManager gm = AppWidgetManager.getInstance(context);
		gm.updateAppWidget(THIS_WIDGET, views);
	}
	
	private static void updateButtons(RemoteViews views, Context context) {
		switch (getWimaxState(context)) {
			case STATE_DISABLED:
				views.setImageViewResource(R.id.btn_wimax, R.drawable.disabled);
				break;
				
			case STATE_ENABLED:
				views.setImageViewResource(R.id.btn_wimax, R.drawable.enabled);
				break;
				
			case STATE_INTERMEDIATE:
				views.setImageViewResource(R.id.btn_wimax, R.drawable.intermediate);
				break;
		}
	}
	
	private static PendingIntent getLaunchPendingIntent(Context context, int appWidgetId, int buttonId) {
		Intent launchIntent = new Intent();
		launchIntent.setClass(context, Toggle4GWidgetProvider.class);
		launchIntent.addCategory(Intent.CATEGORY_ALTERNATIVE);
		launchIntent.setData(Uri.parse("custom:" + buttonId));
		
		PendingIntent pi = PendingIntent.getBroadcast(context, 0, launchIntent, 0);
		
		return pi;
	}
	
	private static int getWimaxState(Context context) {
		int wimaxState = WIMAX_STATE_DISABLED;
		
		try {
			Object wimaxManager = context.getSystemService(CONTEXT_WIMAX_SERVICE);
			Method getWimaxState = wimaxManager.getClass().getMethod("getWimaxState", (Class[]) null);
			wimaxState = (Integer) getWimaxState.invoke(wimaxManager, (Object[]) null);
		}
		catch (Exception e) {
			Log.e(TAG, "could not get wimax state", e);
			wimaxState = WIMAX_STATE_DISABLED;
		}
		
		if (wimaxState == WIMAX_STATE_DISABLED) {
			return STATE_DISABLED;
		}
		else if (wimaxState == WIMAX_STATE_ENABLED) {
			return STATE_ENABLED;
		}
		else {
			return STATE_INTERMEDIATE;
		}
	}
	
	private void toggleWimax(Context context) {
		int wimaxState = getWimaxState(context);
			
		try {
			Object wimaxManager = context.getSystemService(CONTEXT_WIMAX_SERVICE);
			Method setWimaxEnabled = wimaxManager.getClass().getMethod("setWimaxEnabled",
					new Class[] { Boolean.TYPE });
			
			if (wimaxState == STATE_ENABLED) {
				Toast.makeText(context, R.string.turn_off_4g, Toast.LENGTH_SHORT).show();
				setWimaxEnabled.invoke(wimaxManager, new Object[] { Boolean.FALSE });
			}
			else if (wimaxState == STATE_DISABLED) {
				Toast.makeText(context, R.string.turn_on_4g, Toast.LENGTH_LONG).show();
				setWimaxEnabled.invoke(wimaxManager, new Object[] { Boolean.TRUE });
			}
		}
		catch (Exception e) {
			Log.e(TAG, "could not toggle wimax state", e);
			return;
		}
	}
}
